<?php
// +----------------------------------------------------------------------+
// | WR Time Tracker
// +----------------------------------------------------------------------+
// | Copyright (c) 2004-2006 WR Consulting (http://wrconsulting.com)
// +----------------------------------------------------------------------+
// | LIBERAL FREEWARE LICENSE: This source code document may be used
// | by anyone for any purpose, and freely redistributed alone or in
// | combination with other software, provided that the license is obeyed.
// |
// | There are only two ways to violate the license:
// |
// | 1. To redistribute this code in source form, with the copyright
// |    notice or license removed or altered. (Distributing in compiled
// |    forms without embedded copyright notices is permitted).
// |
// | 2. To redistribute modified versions of this code in *any* form
// |    that bears insufficient indications that the modifications are
// |    not the work of the original author(s).
// |
// | This license applies to this document only, not any other software
// | that it may be combined with.
// |
// +----------------------------------------------------------------------+
// | Contributors: Igor Melnik <igor.melnik@mail.ru>
// +----------------------------------------------------------------------+

class Mail {
	var $mSendType;
	var $mCharSet = "iso-8859-1";
	var $mContentType = "text/plain";
	var $mHostName = "localhost";
	var $mSender;
	var $mReceiver;
	var $mReceiverCC;

    function Mail($type='standard') {
    	$this->mSendType = $type;
    }
    
    function setCharSet($value) {
    	$this->mCharSet = $value;
    }
    
    function setContentType($value) {
    	$this->mContentType = $value;
    }
    
    function setHostName($value) {
    	$this->mHostName = $value;
    }
    
    function setReceiver($value) {
    	$this->mReceiver = $value;
    }
    
    function setReceiverCC($value) {
    	$this->mReceiverCC = $value;
    }
    
    function setSender($value) {
    	$this->mSender = $value;
    }
    
    function Send($subject,$data) {
    	$headers = "From: ".$this->mSender."\n";
    	if (isset($this->mReceiverCC)) $headers .= "CC: ".$this->mReceiverCC."\n";
    	//$headers .= "Subject: $subject\n";
    	$headers .= "X-Sender: <".$this->mSender.">\n";
    	$headers .= "X-Mailer: PHP\n";
    	$headers .= "X-Priority: 3 (Normal)\n";
    	$headers .= "Return-Path: <".$this->mSender.">\n";
    	$headers .= "MIME-Version: 1.0\n";
    	$headers .= "Content-Type: ".$this->mContentType."; charset=".$this->mCharSet."\n";
    	//$headers .= "Content-Transfer-Encoding: 8bit";

    	switch ($this->mSendType) {
    		case "standard":
    		mail($this->mReceiver, $subject, $data, $headers);
    		break;
    
    		case "smtp":
    		$smtp = new TSmtp;
    		$data = $headers."\n\n".$data;
    		$smtp->Send($this->mHostName,$this->mSender,$this->mReceiver,$data);
    		unset($smtp);
    		break;
    	}
    }
    
    /**
     * convert to base64-string
     *
     * @param unknown $in_str
     * @param unknown $charset
     * @return unknown
     */
    function mimeEncode($in_str, $charset) {
	   $out_str = $in_str;
	   if ($out_str && $charset) {
	
	       $end = "?=";
	       $start = "=?" . strtoupper($charset) . "?B?";
	       $spacer = $end . "\r\n " . $start;
	
	       $length = 75 - strlen($start) - strlen($end);
	       $length = floor($length/2) * 2;
	
	       //$out_str = base64_encode($out_str);
	       $out_str = Mail::encodemime($out_str,"base64");
	       //$out_str = chunk_split($out_str, $length, $spacer);
	
	       //$spacer = preg_quote($spacer);
	       //$out_str = preg_replace("/" . $spacer . "$/", "", $out_str);
	       $out_str = $start . $out_str . $end;
	   }
	   return $out_str;
	}
	
	function encodemime($text, $encoding) {
	    if($encoding == "quoted-printable")
	    {
	        $nt = "";
	        for($i = 0; $i < strlen($text); $i++)
	        {
	            $c = substr($text, $i, 1);
	            if(($c == "=") || (ord($c) >= 128))
	                $nt .= "=" . dechex(ord($c));
	            else
	                $nt .= $c;
	        }
	        return($nt);
	    }
	    if($encoding == "base64")
	        return(base64_encode($text));
	    return($text);
	}
}

class TSmtp {
  var $mFp = false;
  var $mLastMsg = "";
  var $mError = false;


  function ReadLine() {
    $ret = false;
	$line = fgets($this->mFp,1024);
	if (ereg("^([0-9]+).(.*)$", $line, &$data)) {
	  $recv_code = $data[1];
	  $recv_msg = $data[2];
	  $ret = array($recv_code,$recv_msg);
	}
	return $ret;
  }


  function Dialogue($code, $cmd) {
    $ret = true;
    if (!$this->mError) {
	fwrite( $this->mFp, $cmd . "\r\n" );
	$line = $this->ReadLine();
	if ($line == false) {
	  $this->LastMsg = "";
	  $ret = false;
	} else {
	  $this->LastMsg = "$line[0] $line[1]";
	  if ($line[0] != $code) $ret = false;
	}
	} //if !Error
	return $ret;
  }


  function ErrorMessage($errorMsg="") {
  	$this->mError = true;
	if ($errorMsg) {
		echo $errorMsg."<br>";
	} else {
	    echo "SMTP protocol failure (".$this->LastMsg.").<br>";
	}
	return true;
  }


  function CrlfEncode($data) {
    $data .= "\n";
	$data = str_replace("\n", "\r\n", str_replace("\r", "", $data));
	$data = str_replace("\n.\r\n", "\n. \r\n", $data);
	return $data;
  }

  function HandleEmail($from, $to, $data) {
    $rcpts = explode(",",$to);
	if ( !$this->Dialogue(250,"HELO #phpclient") ) $this->ErrorMessage();
	if ( !$this->Dialogue(250,"MAIL FROM:$from") ) $this->ErrorMessage();
	for ($i = 0; !$err && $i < count($rcpts); $i++) {
	  if (!$this->Dialogue(250,"RCPT TO:$rcpts[$i]")) $this->ErrorMessage();
	}
	if ( !$this->Dialogue(354, "DATA") || !fwrite($this->mFp,$data) || 
		 !$this->Dialogue(250,"\r\n.") || !$this->Dialogue(221, "QUIT")) {
	  $this->ErrorMessage();
	}
	return $this->mError;
  }


  function Connect($hostname) {
	$this->mFp = fsockopen($hostname,25);
	if (!$this->mFp) $this->ErrorMessage("Cannot open socket<br>\n");
	return !$this->mError;
  }


  function Send($hostname,$from,$to,$data,$crlfEncode = 0) {
    if (!$this->Connect($hostname)) return false;
	$line = $this->ReadLine();
	if ( $line && $line[0] == "220" ) {
	  if ($crlfEncode) {
	    $data = $this->CrlfEncode($data);
	  }
	  $this->HandleEmail($from,$to,$data);
	} else {
	  $this->ErrorMessage();
	}
	fclose($this->mFp);
	return $this->mError;
  }
}
?>